<?php
require_once dirname(__FILE__) . '/../../lib/Slim/Slim.php';
require_once 'utils.php';
require_once 'slimUtils.php';
require_once 'resp.php';
require_once 'db.php';
require_once 'error.php';
require_once 'log4php/Logger.php';
require_once 'ex.php';

\Slim\Slim::registerAutoloader();

$app = new \Slim\Slim();

/**
 * function postError
 * Reports an error appened in the client web application.
 */
$app->post('/error', function(){
	$j = getPostJSONPayload();
	if(is_null($j) || empty($j)){
		$err = emptyPayloadError('postError[rest.php]');
		Response::finalizeError(Response::CODE_FATAL_ERROR, $err);
		return;
	}

	getErrorFromJSON($j)->report();
	Response::finalizeMessage(Response::CODE_SUCCESS, 'The error has been saved');
});

/**
 * getUser
 * Checks if the user has already been registered.
 * @param id the Facebook id of the user.
 * @return a Json object containing the result of the DB query.
 */
$app->get('/user/:id', function($id){
	try {
		$user = NULL;
		if(DBManager::existSonnaUser($id))
			$user = getUser($id);

		$result = array();
		$result['result'] = Response::CODE_SUCCESS;
		$result['alreadyRegistered'] = !empty($user);
		$result['message'] = 'query executed successfuly';
		$result['user'] = $user;
		Response::finalizeResponse(Response::CODE_SUCCESS, $result);
	} catch(PDOException $e) {
		$log = getLogger();
		$log->info($e->getMessage());
		$error = new Error(
			$e->getMessage(),
			'getUser[rest.php]',
			$id,
			Error::LVL_ERROR
		);

		Response::finalizeError(Response::CODE_ERROR_DB_SELECT_FAILED, $error);
	} catch(DBException $e) {
		$log = getLogger();
		$log->info($e->getMessage());
		$error = new Error(
			$e->getMessage(),
			'getUser[rest.php]',
			$id,
			Error::LVL_ERROR
		);

		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
	}
});


/**
 * function postUser
 * Inserts a new user in the fxb database.
 * The user facebook profile is retrieved in the request body.
 * All the fields contained in the profile are dumped in the db.
 */
$app->post('/user', function() {
	$user = getPostJSONPayload();

	if(is_null($user)){
		$err = emptyPayloadError('postUser[rest.php]');
		Response::finalizeError(Response::CODE_FATAL_ERROR, $err);
		return;
	}

	try {
		if(checkSonnaUser($user['id'])){
			Response::finalizeMessage(Response::CODE_SUCCESS, "The user had already been added to the database");
			return;
		}

		$stmt_fbUser = DBManager::statementInsertOrUpdateFBUser();

		$keys = array('id', 'name', 'first_name', 'last_name', 'link', 'username', 'birthday', 'hometown', 'location', 'bio', 'quotes', 'work', 'sports', 'favorite_teams', 'favorite_athletes', 'education', 'gender', 'relationship_status', 'religion', 'political', 'email', 'website', 'timezone', 'locale', 'verified', 'updated_time');
		$tmpVal;
		for ($i = 0; $i < count($keys); $i++) {
$tmpVal = getArrayValue($user, $keys[$i]);

			//echo $keys[$i].' => ' . $tmpVal . '\n';

			$stmt_fbUser->bindValue(':'.$keys[$i], $tmpVal);
			if(!(strcmp($keys[$i], 'id') == 0 ||
				strcmp($keys[$i], 'name') == 0 ||
				strcmp($keys[$i], 'first_name') == 0 ||
				strcmp($keys[$i], 'last_name') == 0 ||
				strcmp($keys[$i], 'username') == 0 ||
				strcmp($keys[$i], 'gender') == 0 ||
				strcmp($keys[$i], 'locale') == 0)){
				$stmt_fbUser->bindValue(':u'.$keys[$i], $tmpVal);
			}
				
		}
		global $app;
		$headers = $app->request()->headers();
		$from =$headers['REFERER'];

		$stmt_sonnaUser = DBManager::statementInsertSonnaUser();
		$stmt_sonnaUser->bindValue(':fid', $user['id']);
		$stmt_sonnaUser->bindValue(':from', $from);
		$stmt_sonnaUser->bindValue(':drupal_user', intval($user['drupal_user']));
		var_dump($user['drupal_user']);
//var_dump($user)d;
		echo("begin update");
		DBManager::beginTransaction();
		$stmt_fbUser->execute();
//$stmt_fbUser->debugDumpParams();
		$stmt_fbUser->closeCursor();

		echo('FBUser inserted');
		$stmt_sonnaUser->execute();
		$stmt_sonnaUser->closeCursor();

		echo('SonnaUser inserted');
		DBManager::commitTransaction();

		Response::finalizeMessage(Response::CODE_SUCCESS, "The user has been inserted in the database");
	} catch(PDOException $e) {
		DBManager::rollBack();
		$error = new Error(
			$e->getMessage(),
			'postUser[rest.php]',
			$user['id'],
			Error::LVL_ERROR
		);

		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
	}
});

/**
 * function postFriends
 * Receives a list of friends and stores it into the database.
 */
$app->post('/user/friends', function(){
	$j = getPostJSONPayload();
	if(is_null($j) || empty($j)){
		$err = emptyPayloadError('postFriends[rest.php]');
		Response::finalizeError(Response::CODE_FATAL_ERROR, $err);
		return;
	}
//	var_dump($j);
	try {
		$uid = $j['id'];
		$stmt = DBManager::statementInsertFriend();
		foreach($j['data'] as $friend){
			$stmt->bindValue(':uid', $uid, PDO::PARAM_STR);
			$stmt->bindValue(':fid', $friend['id'], PDO::PARAM_STR);
			$stmt->bindValue(':name', $friend['name'], PDO::PARAM_STR);

			$stmt->execute();
		}
		$stmt->closeCursor();
	} catch (PDOException $e){
		$error = new Error(
			$e->getMessage(),
			'postFriends[rest.php]',
			$uid,
			Error::LVL_ERROR
		);
		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
	}

});

/**
 * function postSearch
 * Receives a JSON object containing information about search made by the user
 * and stores it in the database.
 */
$app->post('/user/search', function() {
	$payload = getPostJSONPayload();

	if(is_null($payload)){
		$err = emptyPayloadError('postSearch[rest.php]');
		Response::finalizeError(Response::CODE_FATAL_ERROR, $err);
		return;
	}

	try {
		$stmt = DBManager::statementInsertSearch();

		$stmt->bindValue(':uid', $payload['uid']);
		$stmt->bindValue(':search', $payload['search']);
		$stmt->bindValue(':engine', $payload['engine']);

		$stmt->execute();
		$stmt->closeCursor();
		Response::finalizeMessage(Response::CODE_SUCCESS, "The search has been inserted in the database");
	} catch(PDOException $e) {
		$error = new Error(
			$e->getMessage(),
			'postUser[rest.php]',
			$user['id'],
			Error::LVL_ERROR
		);

		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
	}
});

/**
 * putToken
 * Aggiorna l'access token dell'utente specificato.
 * @param id facebook user id
 * @param token short term access token
 */
$app->put('/user/:id/token/:token', function($id, $token){
	$ch = curl_init(getFBUrlExtendedToken($token));
	curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
	curl_setopt($ch, CURLOPT_HEADER, false);
	curl_setopt($ch, CURLOPT_FRESH_CONNECT, true);
	$data = curl_exec($ch);
	curl_close($ch);

	$error = null;

	if(!$data){
		$error = new Error(
			'Non è stato possibile recuperare un extended access token.',
			'putToken[rest.php]',
			$id,
			Error::LVL_FATAL
		);
	}

	$result = array();
	parse_str($data, $result);

	if(empty($result))
		$error = new Error(
			'Errore nel parsing della risposta di facebook',
			'putToken[rest.php]',
			$id,
			Error::LVL_FATAL
		);
	
	if(empty($result['access_token']))
		$error = new Error(
			'La stringa restituita da Facebook non contiene una chiave `access_token`\n'.$data,
			'putToken[rest.php]',
			$id,
			Error::LVL_FATAL
		);
		
	if(!is_null($error)){
		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
		return;
	}

	try {
		$stmt = DBManager::statementInsertOrUpdateToken();

		$stmt->bindValue(':id', $id);
		$stmt->bindValue(':token', $result['access_token']);
		$stmt->bindValue(':update', $result['access_token']);

		$stmt->execute();
		$stmt->closeCursor();
		Response::finalizeMessage(Response::CODE_SUCCESS, "The search has been inserted in the database");
	} catch(PDOException $e) {
		$error = new Error(
			$e->getMessage(),
			'putToken[rest.php]',
			$id,
			Error::LVL_ERROR
		);
		Response::finalizeError(Response::CODE_ERROR_DB_INSERT_FAILED, $error);
	}
});

/*$app->post('/user/post', function ($user, $post) {
	$sql_insert = "INSERT INTO posts (content, uid) VALUES (:post, :user)";

	try {
		$db = getConnection();
		$stmt = $db->prepare($sql_insert);
		$stmt->bindValue("user", $user);
		$stmt->bindValue("post", $post);
		$stmt->execute();
		$stmt->closeCursor();
		$db = null;
		Response::finalizeMessage(Response::CODE_SUCCESS, "The post has been inserted in the database");
	} catch(PDOException $e) {
		Response::finalizeMessage(Response::CODE_ERROR_DB_INSERT_FAILED, $e->getMessage());
	}
});*/

$app->run();
?>
